package org.jjche.sys.modules.fillrule.service;

import lombok.RequiredArgsConstructor;
import org.jjche.common.exception.util.AssertUtil;
import org.jjche.common.param.MyPage;
import org.jjche.common.param.PageParam;
import org.jjche.common.util.FileUtil;
import org.jjche.mybatis.base.service.MyServiceImpl;
import org.jjche.sys.enums.SysErrorCodeEnum;
import org.jjche.sys.modules.fillrule.domain.SysFillRuleDO;
import org.jjche.sys.modules.fillrule.dto.SysFillRuleDTO;
import org.jjche.sys.modules.fillrule.dto.SysFillRuleQueryCriteriaDTO;
import org.jjche.sys.modules.fillrule.mapper.SysFillRuleMapper;
import org.jjche.sys.modules.fillrule.mapstruct.SysFillRuleMapStruct;
import org.jjche.sys.modules.fillrule.vo.SysFillRuleVO;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;

import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.ArrayList;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;

import static org.jjche.common.exception.util.BusinessExceptionUtil.exception;


/**
 * <p>
 * 系统编码规则 服务实现类
 * </p>
 *
 * @author miaoyj
 * @since 2024-05-11
 */
@Service
@RequiredArgsConstructor
public class SysFillRuleService extends MyServiceImpl<SysFillRuleMapper, SysFillRuleDO> {

    private final SysFillRuleMapStruct sysFillRuleMapStruct;

    /**
     * <p>
     * 创建
     * </p>
     *
     * @param dto 创建对象
     * @return id
     */
    @Transactional(rollbackFor = Exception.class)
    public Long save(SysFillRuleDTO dto) {
        //唯一索引验证
        String code = dto.getCode();
        SysFillRuleDO dbDO = this.baseMapper.getByCode(code);
        AssertUtil.isTrue(dbDO == null, SysErrorCodeEnum.FILL_RULE_NAME_ALREADY_ERROR, code);
        SysFillRuleDO sysFillRuleDO = this.sysFillRuleMapStruct.toDO(dto);
        AssertUtil.isTrue(this.save(sysFillRuleDO), SysErrorCodeEnum.SAVE_ERROR);
        return sysFillRuleDO.getId();
    }

    /**
     * <p>
     * 多选删除
     * </p>
     *
     * @param ids 主键
     */
    @Transactional(rollbackFor = Exception.class)
    public void delete(List<Long> ids) {
        AssertUtil.isTrue(this.removeBatchByIds(ids), SysErrorCodeEnum.DELETE_ERROR);
    }

    /**
     * <p>
     * 编辑
     * </p>
     *
     * @param dto 编辑对象
     */
    @Transactional(rollbackFor = Exception.class)
    public void update(SysFillRuleDTO dto) {
        SysFillRuleDO sysFillRuleDO = this.getById(dto.getId());
        AssertUtil.notNull(sysFillRuleDO, SysErrorCodeEnum.RECORD_NOT_FOUND);
        //唯一索引验证
        String code = dto.getCode();
        Long id = dto.getId();
        SysFillRuleDO dbDO = this.baseMapper.getByCodeAndNeId(code, id);
        AssertUtil.isTrue(dbDO == null, SysErrorCodeEnum.FILL_RULE_NAME_ALREADY_ERROR, code);
        sysFillRuleDO = this.sysFillRuleMapStruct.toDO(dto);
        AssertUtil.isTrue(this.updateById(sysFillRuleDO), SysErrorCodeEnum.UPDATE_ERROR);
    }

    /**
     * <p>
     * 根据ID查询
     * </p>
     *
     * @param id ID
     * @return SysFillRuleVO 对象
     */
    public SysFillRuleVO getVoById(Long id) {
        SysFillRuleDO sysFillRuleDO = this.getById(id);
        AssertUtil.notNull(sysFillRuleDO, SysErrorCodeEnum.RECORD_NOT_FOUND);
        return this.sysFillRuleMapStruct.toVO(sysFillRuleDO);
    }

    /**
     * <p>
     * 查询数据分页
     * </p>
     *
     * @param query 条件
     * @param page  分页
     * @return SysFillRuleVO 分页
     */
    public MyPage<SysFillRuleVO> page(PageParam page, SysFillRuleQueryCriteriaDTO query) {
        return this.baseMapper.page(page, query);
    }

    /**
     * <p>
     * 查询所有数据不分页
     * </p>
     *
     * @param query 条件
     * @return SysFillRuleVO 列表对象
     */
    public List<SysFillRuleVO> list(SysFillRuleQueryCriteriaDTO query) {
        List<SysFillRuleDO> list = this.baseMapper.list(query);
        return sysFillRuleMapStruct.toVO(list);
    }

    /**
     * <p>
     * 导出数据
     * </p>
     *
     * @param query 条件
     */
    public void download(SysFillRuleQueryCriteriaDTO query) {
        List<Map<String, Object>> list = new ArrayList<>();
        List<SysFillRuleVO> all = this.list(query);
        for (SysFillRuleVO sysFillRule : all) {
            Map<String, Object> map = new LinkedHashMap<>();
            map.put("名称", sysFillRule.getName());
            map.put("Code", sysFillRule.getCode());
            map.put("实现类", sysFillRule.getRuleClass());
            map.put("参数", sysFillRule.getParams());
            list.add(map);
        }
        try {
            HttpServletResponse httpServletResponse = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getResponse();
            FileUtil.downloadExcel(list, httpServletResponse);
        } catch (IOException e) {
            throw exception(SysErrorCodeEnum.FILE_EXPORT_ERROR);
        }
    }
}
